GeezerVisonThe World Wide Web, restored to 800 pixels of glory. |
| Home|About|Gaming cabinet|Archives|How it works|Starter sites |
GeezerVison is showing packaging.python.org — Version specifiers - Python Packaging User Guide Version specifiers¶This specification describes a scheme for identifying versions of Python software distributions, and declaring dependencies on particular versions. Definitions¶The key words “MUST”, “MUST NOT”, “REQUIRED”, “SHALL”, “SHALL NOT”, “SHOULD”, “SHOULD NOT”, “RECOMMENDED”, “MAY”, and “OPTIONAL” in this document are to be interpreted as described in RFC 2119. “Build tools” are automated tools intended to run on development systems, producing source and built distribution archives. Build tools may also be invoked by integration tools in order to build software distributed as sdists rather than built distribution archives. “Index servers” are active distribution registries which publish version and dependency metadata and place constraints on the permitted metadata. “Publication tools” are automated tools intended to run on development systems and upload source and built distribution archives to index servers. “Installation tools” are integration tools specifically intended to run on deployment targets, consuming source and built distribution archives from an index server or other designated location and deploying them to the target system. “Automated tools” is a collective term covering build tools, index servers, publication tools, integration tools and any other software that produces or consumes distribution version and dependency metadata. Version scheme¶Distributions are identified by a public version identifier which supports all defined version comparison operations The version scheme is used both to describe the distribution version provided by a particular distribution archive, as well as to place constraints on the version of dependencies needed in order to build or run the software. Public version identifiers¶The canonical public version identifiers MUST comply with the following scheme: [N!]N(.N)*[{a|b|rc}N][.postN][.devN]
Public version identifiers MUST NOT include leading or trailing whitespace. Public version identifiers MUST be unique within a given distribution. Installation tools SHOULD ignore any public versions which do not comply with this scheme but MUST also include the normalizations specified below. Installation tools MAY warn the user when non-compliant or ambiguous versions are detected. See also Appendix: Parsing version strings with regular expressions which provides a regular expression to check strict conformance with the canonical format, as well as a more permissive regular expression accepting inputs that may require subsequent normalization. Public version identifiers are separated into up to five segments:
Any given release will be a “final release”, “pre-release”, “post-release” or “developmental release” as defined in the following sections. All numeric components MUST be non-negative integers represented as sequences of ASCII digits. All numeric components MUST be interpreted and ordered according to their numeric value, not as text strings. All numeric components MAY be zero. Except as described below for the release segment, a numeric component of zero has no special significance aside from always being the lowest possible value in the version ordering. Note Some hard to read version identifiers are permitted by this scheme in order to better accommodate the wide range of versioning practices across existing public and private Python projects. Accordingly, some of the versioning practices which are technically permitted by the specification are strongly discouraged for new projects. Where this is the case, the relevant details are noted in the following sections. Local version identifiers¶Local version identifiers MUST comply with the following scheme: <public version identifier>[+<local version label>] They consist of a normal public version identifier (as defined in the previous section), along with an arbitrary “local version label”, separated from the public version identifier by a plus. Local version labels have no specific semantics assigned, but some syntactic restrictions are imposed. Local version identifiers are used to denote fully API (and, if applicable, ABI) compatible patched versions of upstream projects. For example, these may be created by application developers and system integrators by applying specific backported bug fixes when upgrading to a new upstream release would be too disruptive to the application or other integrated system (such as a Linux distribution). The inclusion of the local version label makes it possible to differentiate upstream releases from potentially altered rebuilds by downstream integrators. The use of a local version identifier does not affect the kind of a release but, when applied to a source distribution, does indicate that it may not contain the exact same code as the corresponding upstream release. To ensure local version identifiers can be readily incorporated as part of filenames and URLs, and to avoid formatting inconsistencies in hexadecimal hash representations, local version labels MUST be limited to the following set of permitted characters:
Local version labels MUST start and end with an ASCII letter or digit. Comparison and ordering of local versions considers each segment of the local
version (divided by a An “upstream project” is a project that defines its own public versions. A “downstream project” is one which tracks and redistributes an upstream project, potentially backporting security and bug fixes from later versions of the upstream project. Local version identifiers SHOULD NOT be used when publishing upstream projects to a public index server, but MAY be used to identify private builds created directly from the project source. Local version identifiers SHOULD be used by downstream projects when releasing a version that is API compatible with the version of the upstream project identified by the public version identifier, but contains additional changes (such as bug fixes). As the Python Package Index is intended solely for indexing and hosting upstream projects, it MUST NOT allow the use of local version identifiers. Final releases¶A version identifier that consists solely of a release segment and optionally an epoch identifier is termed a “final release”. The release segment consists of one or more non-negative integer values, separated by dots: N(.N)* Final releases within a project MUST be numbered in a consistently increasing fashion, otherwise automated tools will not be able to upgrade them correctly. Comparison and ordering of release segments considers the numeric value of each component of the release segment in turn. When comparing release segments with different numbers of components, the shorter segment is padded out with additional zeros as necessary. While any number of additional components after the first are permitted under this scheme, the most common variants are to use two components (“major.minor”) or three components (“major.minor.micro”). For example: 0.9 0.9.1 0.9.2 ... 0.9.10 0.9.11 1.0 1.0.1 1.1 2.0 2.0.1 ... A release series is any set of final release numbers that start with a
common prefix. For example, Note
Date-based release segments are also permitted. An example of a date-based release scheme using the year and month of the release: 2012.4 2012.7 2012.10 2013.1 2013.6 ... Pre-releases¶Some projects use an “alpha, beta, release candidate” pre-release cycle to support testing by their users prior to a final release. If used as part of a project’s development cycle, these pre-releases are indicated by including a pre-release segment in the version identifier: X.YaN # Alpha release X.YbN # Beta release X.YrcN # Release Candidate X.Y # Final release A version identifier that consists solely of a release segment and a pre-release segment is termed a “pre-release”. The pre-release segment consists of an alphabetical identifier for the pre-release phase, along with a non-negative integer value. Pre-releases for a given release are ordered first by phase (alpha, beta, release candidate) and then by the numerical component within that phase. Installation tools MAY accept both Installation tools SHOULD interpret Build tools, publication tools and index servers SHOULD disallow the creation
of both Post-releases¶Some projects use post-releases to address minor errors in a final release that do not affect the distributed software (for example, correcting an error in the release notes). If used as part of a project’s development cycle, these post-releases are indicated by including a post-release segment in the version identifier: X.Y.postN # Post-release A version identifier that includes a post-release segment without a developmental release segment is termed a “post-release”. The post-release segment consists of the string Note The use of post-releases to publish maintenance releases containing actual bug fixes is strongly discouraged. In general, it is better to use a longer release number and increment the final component for each maintenance release. Post-releases are also permitted for pre-releases: X.YaN.postM # Post-release of an alpha release X.YbN.postM # Post-release of a beta release X.YrcN.postM # Post-release of a release candidate Note Creating post-releases of pre-releases is strongly discouraged, as it makes the version identifier difficult to parse for human readers. In general, it is substantially clearer to simply create a new pre-release by incrementing the numeric component. Developmental releases¶Some projects make regular developmental releases, and system packagers (especially for Linux distributions) may wish to create early releases directly from source control which do not conflict with later project releases. If used as part of a project’s development cycle, these developmental releases are indicated by including a developmental release segment in the version identifier: X.Y.devN # Developmental release A version identifier that includes a developmental release segment is termed a “developmental release”. The developmental release segment consists of the string Developmental releases are also permitted for pre-releases and post-releases: X.YaN.devM # Developmental release of an alpha release X.YbN.devM # Developmental release of a beta release X.YrcN.devM # Developmental release of a release candidate X.Y.postN.devM # Developmental release of a post-release Do note that development releases are considered a type of pre-release when handling them. Note While they may be useful for continuous integration purposes, publishing developmental releases of pre-releases to general purpose public index servers is strongly discouraged, as it makes the version identifier difficult to parse for human readers. If such a release needs to be published, it is substantially clearer to instead create a new pre-release by incrementing the numeric component. Developmental releases of post-releases are also strongly discouraged, but they may be appropriate for projects which use the post-release notation for full maintenance releases which may include code changes. Version epochs¶If included in a version identifier, the epoch appears before all other components, separated from the release segment by an exclamation mark: E!X.Y # Version identifier with epoch If no explicit epoch is given, the implicit epoch is Most version identifiers will not include an epoch, as an explicit epoch is
only needed if a project changes the way it handles version numbering in
a way that means the normal version ordering rules will give the wrong
answer. For example, if a project is using date based versions like
1.0 1.1 2.0 2013.10 2014.04 However, by specifying an explicit epoch, the sort order can be changed appropriately, as all versions from a later epoch are sorted after versions from an earlier epoch: 2013.10 2014.04 1!1.0 1!1.1 1!2.0 Note Use of nonzero epochs is discouraged. They are often not supported or discouraged by downstream packaging where Python packages may need to be consumed, and due to their scarce use they may also not be well supported by Python packaging tools. When version scheme needs to be changed, it is preferable to continue with monotonically increasing numbers in epoch zero. For example, the version 2026.x could be unambiguously followed by 3000.x. See Discouraging use of epoch segments in versions for the relevant discussion. Normalization¶In order to maintain better compatibility with existing versions there are a number of “alternative” syntaxes that MUST be taken into account when parsing versions. These syntaxes MUST be considered when parsing a version, however they should be “normalized” to the standard syntax defined above. Case sensitivity¶All ascii letters should be interpreted case insensitively within a version and
the normal form is lowercase. This allows versions such as Integer Normalization¶All integers are interpreted via the Pre-release separators¶Pre-releases should allow a Pre-release spelling¶Pre-releases allow the additional spellings of Implicit pre-release number¶Pre releases allow omitting the numeral in which case it is implicitly assumed
to be Post release separators¶Post releases allow a Post release spelling¶Post-releases allow the additional spellings of Implicit post release number¶Post releases allow omitting the numeral in which case it is implicitly assumed
to be Implicit post releases¶Post releases allow omitting the Development release separators¶Development releases allow a Implicit development release number¶Development releases allow omitting the numeral in which case it is implicitly
assumed to be Local version segments¶With a local version, in addition to the use of Preceding v character¶In order to support the common version notation of Leading and Trailing Whitespace¶Leading and trailing whitespace must be silently ignored and removed from all
normalized forms of a version. This includes Examples of compliant version schemes¶The standard version scheme is designed to encompass a wide range of identification practices across public and private Python projects. In practice, a single project attempting to use the full flexibility offered by the scheme would create a situation where human users had difficulty figuring out the relative order of versions, even though the rules above ensure all compliant tools will order them consistently. The following examples illustrate a small selection of the different approaches projects may choose to identify their releases, while still ensuring that the “latest release” and the “latest stable release” can be easily determined, both by human users and automated tools. Simple “major.minor” versioning: 0.1 0.2 0.3 1.0 1.1 ... Simple “major.minor.micro” versioning: 1.1.0 1.1.1 1.1.2 1.2.0 ... “major.minor” versioning with alpha, beta and candidate pre-releases: 0.9 1.0a1 1.0a2 1.0b1 1.0rc1 1.0 1.1a1 ... “major.minor” versioning with developmental releases, release candidates and post-releases for minor corrections: 0.9 1.0.dev1 1.0.dev2 1.0.dev3 1.0.dev4 1.0rc1 1.0rc2 1.0 1.0.post1 1.1.dev1 ... Date based releases, using an incrementing serial within each year, skipping zero: 2012.1 2012.2 2012.3 ... 2012.15 2013.1 2013.2 ... Summary of permitted suffixes and relative ordering¶Note This section is intended primarily for authors of tools that automatically process distribution metadata, rather than developers of Python distributions deciding on a versioning scheme. The epoch segment of version identifiers MUST be sorted according to the
numeric value of the given epoch. If no epoch segment is present, the
implicit numeric value is The release segment of version identifiers MUST be sorted in the same order as Python’s tuple sorting when the normalized release segment is parsed as follows: tuple(map(int, release_segment.split(".")))
All release segments involved in the comparison MUST be converted to a consistent length by padding shorter segments with zeros as needed. Within a numeric release ( .devN, aN, bN, rcN, <no suffix>, .postN Note that Within an alpha ( .devN, <no suffix>, .postN Within a post-release ( .devN, <no suffix> Note that Within a pre-release, post-release or development release segment with a shared prefix, ordering MUST be by the value of the numeric component. The following example covers many of the possible combinations: 1.dev0 1.0.dev456 1.0a1 1.0a2.dev456 1.0a12.dev456 1.0a12 1.0b1.dev456 1.0b2 1.0b2.post345.dev456 1.0b2.post345 1.0rc1.dev456 1.0rc1 1.0 1.0+abc.5 1.0+abc.7 1.0+5 1.0.post456.dev34 1.0.post456 1.0.15 1.1.dev1 Version ordering across different metadata versions¶Metadata v1.0 (PEP 241) and metadata v1.1 (PEP 314) do not specify a standard version identification or ordering scheme. However metadata v1.2 (PEP 345) does specify a scheme which is defined in PEP 386. Due to the nature of the simple installer API it is not possible for an installer to be aware of which metadata version a particular distribution was using. Additionally installers required the ability to create a reasonably prioritized list that includes all, or as many as possible, versions of a project to determine which versions it should install. These requirements necessitate a standardization across one parsing mechanism to be used for all versions of a project. Due to the above, this specification MUST be used for all versions of metadata and supersedes PEP 386 even for metadata v1.2. Tools SHOULD ignore any versions which cannot be parsed by the rules in this specification, but MAY fall back to implementation defined version parsing and ordering schemes if no versions complying with this specification are available. Distribution users may wish to explicitly remove non-compliant versions from any private package indexes they control. Compatibility with other version schemes¶Some projects may choose to use a version scheme which requires translation in order to comply with the public version scheme defined in this specification. In such cases, the project specific version can be stored in the metadata while the translated public version is published in the version field. This allows automated distribution tools to provide consistently correct ordering of published releases, while still allowing developers to use the internal versioning scheme they prefer for their projects. Semantic versioning¶Semantic versioning is a popular version identification scheme that is more prescriptive than this specification regarding the significance of different elements of a release number. Even if a project chooses not to abide by the details of semantic versioning, the scheme is worth understanding as it covers many of the issues that can arise when depending on other distributions, and when publishing a distribution that others rely on. The “Major.Minor.Patch” (described in this specification as “major.minor.micro”) aspects of semantic versioning (clauses 1-8 in the 2.0.0 specification) are fully compatible with the version scheme defined in this specification, and abiding by these aspects is encouraged. Semantic versions containing a hyphen (pre-releases - clause 10) or a plus sign (builds - clause 11) are not compatible with this specification and are not permitted in the public version field. One possible mechanism to translate such semantic versioning based source
labels to compatible public versions is to use the Specific build information may also be included in local version labels. DVCS based version labels¶Many build tools integrate with distributed version control systems like Git and Mercurial in order to add an identifying hash to the version identifier. As hashes cannot be ordered reliably such versions are not permitted in the public version field. As with semantic versioning, the public Identifying hash information may also be included in local version labels. Olson database versioning¶The This can be translated to a compliant public version identifier as
As with other translated version identifiers, the corresponding Olson database version could be recorded in the project metadata. Version specifiers¶A version specifier consists of a series of version clauses, separated by commas. For example: ~= 0.9, >= 1.0, != 1.3.4.*, < 2.0 The comparison operator determines the kind of version clause:
The comma (“,”) is equivalent to a logical and operator: a candidate version must match all given version clauses in order to match the specifier as a whole. Whitespace between a conditional operator and the following version identifier is optional, as is the whitespace around the commas. When multiple candidate versions match a version specifier, the preferred version SHOULD be the latest version as determined by the consistent ordering defined by the standard Version scheme. Whether or not pre-releases are considered as candidate versions SHOULD be handled as described in Handling of pre-releases. Except where specifically noted below, local version identifiers MUST NOT be permitted in version specifiers, and local version labels MUST be ignored entirely when checking if candidate versions match a given version specifier. Compatible release¶A compatible release clause consists of the compatible release operator The specified version identifier must be in the standard format described in Version scheme. Local version identifiers are NOT permitted in this version specifier. For a given release identifier >= V.N, == V.* This operator MUST NOT be used with a single segment version number such as
For example, the following groups of version clauses are equivalent: ~= 2.2 >= 2.2, == 2.* ~= 1.4.5 >= 1.4.5, == 1.4.* If a pre-release, post-release or developmental release is named in a
compatible release clause as ~= 2.2.post3 >= 2.2.post3, == 2.* ~= 1.4.5a4 >= 1.4.5a4, == 1.4.* The padding rules for release segment comparisons means that the assumed degree of forward compatibility in a compatible release clause can be controlled by appending additional zeros to the version specifier: ~= 2.2.0 >= 2.2.0, == 2.2.* ~= 1.4.5.0 >= 1.4.5.0, == 1.4.5.* Version matching¶A version matching clause includes the version matching operator The specified version identifier must be in the standard format described in
Version scheme, but a trailing By default, the version matching operator is based on a strict equality comparison: the specified version must be exactly the same as the requested version. The only substitution performed is the zero padding of the release segment to ensure the release segments are compared with the same length. Whether or not strict version matching is appropriate depends on the specific use case for the version specifier. Automated tools SHOULD at least issue warnings and MAY reject them entirely when strict version matches are used inappropriately. Prefix matching may be requested instead of strict comparison, by appending
a trailing For example, given the version == 1.1 # Not equal, so 1.1.post1 does not match clause == 1.1.post1 # Equal, so 1.1.post1 matches clause == 1.1.* # Same prefix, so 1.1.post1 matches clause For purposes of prefix matching, the pre-release segment is considered to
have an implied preceding == 1.1 # Not equal, so 1.1a1 does not match clause == 1.1a1 # Equal, so 1.1a1 matches clause == 1.1.* # Same prefix, so 1.1a1 matches clause if pre-releases are requested An exact match is also considered a prefix match (this interpretation is
implied by the usual zero padding rules for the release segment of version
identifiers). Given the version == 1.1 # Equal, so 1.1 matches clause == 1.1.0 # Zero padding expands 1.1 to 1.1.0, so it matches clause == 1.1.dev1 # Not equal (dev-release), so 1.1 does not match clause == 1.1a1 # Not equal (pre-release), so 1.1 does not match clause == 1.1.post1 # Not equal (post-release), so 1.1 does not match clause == 1.1.* # Same prefix, so 1.1 matches clause It is invalid to have a prefix match containing a development or local release
such as The use of If the specified version identifier is a public version identifier (no local version label), then the local version label of any candidate versions MUST be ignored when matching versions. If the specified version identifier is a local version identifier, then the local version labels of candidate versions MUST be considered when matching versions, with the public version identifier being matched as described above, and the local version label being checked for equivalence using a strict string equality comparison. Version exclusion¶A version exclusion clause includes the version exclusion operator The allowed version identifiers and comparison semantics are the same as those of the Version matching operator, except that the sense of any match is inverted. For example, given the version != 1.1 # Not equal, so 1.1.post1 matches clause != 1.1.post1 # Equal, so 1.1.post1 does not match clause != 1.1.* # Same prefix, so 1.1.post1 does not match clause Inclusive ordered comparison¶An inclusive ordered comparison clause includes a comparison operator and a version identifier, and will match any version where the comparison is correct based on the relative position of the candidate version and the specified version given the consistent ordering defined by the standard Version scheme. The inclusive ordered comparison operators are As with version matching, the release segment is zero padded as necessary to ensure the release segments are compared with the same length. Local version identifiers are NOT permitted in this version specifier. Exclusive ordered comparison¶The exclusive ordered comparisons The exclusive ordered comparison The exclusive ordered comparison The exclusive ordered comparison As with version matching, the release segment is zero padded as necessary to ensure the release segments are compared with the same length. Local version identifiers are NOT permitted in this version specifier. Arbitrary equality¶Arbitrary equality comparisons are simple string equality operations which do
not take into account any of the semantic information such as zero padding or
local versions. The comparison MUST treat ASCII letters case-insensitively, e.g.
by lowercasing, and is unspecified for non-ASCII text. This operator also does
not support prefix matching as the The primary use case for arbitrary equality is to allow for specifying a version which cannot otherwise be represented by this specification. This operator is special and acts as an escape hatch to allow someone using a tool which implements this specification to still install a legacy version which is otherwise incompatible with this specification. An example would be This operator may also be used to explicitly require an unpatched version
of a project such as Use of this operator is heavily discouraged and tooling MAY display a warning when it is used. Handling of pre-releases¶Pre-releases of any kind, including developmental releases, are implicitly excluded from all version specifiers, unless they are already present on the system, explicitly requested by the user, or if the only available version that satisfies the version specifier is a pre-release. By default, dependency resolution tools SHOULD:
Dependency resolution tools MAY issue a warning if a pre-release is needed to satisfy a version specifier. Dependency resolution tools SHOULD also allow users to request the following alternative behaviours:
Dependency resolution tools MAY also allow the above behaviour to be controlled on a per-distribution basis. Post-releases and final releases receive no special treatment in version specifiers - they are always included unless explicitly excluded. Examples¶
Direct references¶Some automated tools may permit the use of a direct reference as an
alternative to a normal version specifier. A direct reference consists of
the specifier Whether or not direct references are appropriate depends on the specific use case for the version specifier. Automated tools SHOULD at least issue warnings and MAY reject them entirely when direct references are used inappropriately. Public index servers SHOULD NOT allow the use of direct references in uploaded distributions. Direct references are intended as a tool for software integrators rather than publishers. Depending on the use case, some appropriate targets for a direct URL reference may be an sdist or a wheel. The exact URLs and targets supported will be tool dependent. For example, a local source archive may be referenced directly: pip @ file:///localbuilds/pip-1.3.1.zip Alternatively, a prebuilt archive may also be referenced: pip @ file:///localbuilds/pip-1.3.1-py33-none-any.whl All direct references that do not refer to a local file URL SHOULD specify
a secure transport mechanism (such as It is RECOMMENDED that only hashes which are unconditionally provided by
the latest version of the standard library’s For source archive and wheel references, an expected hash value may be
specified by including a For version control references, the To handle version control systems that do not support including commit or
tag references directly in the URL, that information may be appended to the
end of the URL using the Note This isn’t quite the same as the existing VCS reference notation supported by pip. Firstly, the distribution name is moved in front rather than embedded as part of the URL. Secondly, the commit hash is included even when retrieving based on a tag, in order to meet the requirement above that every link should include a hash to make things harder to forge (creating a malicious repo with a particular tag is easy, creating one with a specific hash, less so). Remote URL examples: pip @ https://github.com/pypa/pip/archive/1.3.1.zip#sha1=da9234ee9982d4bbb3c72346a6de940a148ea686 pip @ git+https://github.com/pypa/pip.git@7921be1537eac1e97bc40179a57f0349c2aee67d pip @ git+https://github.com/pypa/[email protected]#7921be1537eac1e97bc40179a57f0349c2aee67d File URLs¶File URLs take the form of On the various *nix operating systems the only allowed values for On Windows the file format should include the drive letter if applicable as
part of the Summary of differences from pkg_resources.parse_version¶
Appendix: Parsing version strings with regular expressions¶As noted earlier in the Public version identifiers section, published version identifiers SHOULD use the canonical format. This section provides regular expressions that can be used to test whether a version is already in that form, and if it’s not, extract the various components for subsequent normalization. To test whether a version identifier is in the canonical format, you can use the following function: import re def is_canonical(version): return re.match(r'^([1-9][0-9]*!)?(0|[1-9][0-9]*)(\.(0|[1-9][0-9]*))*((a|b|rc)(0|[1-9][0-9]*))?(\.post(0|[1-9][0-9]*))?(\.dev(0|[1-9][0-9]*))?$', version) is not None To extract the components of a version identifier, use the following regular expression (as defined by the packaging project): VERSION_PATTERN = r""" v? (?: (?:(?P<epoch>[0-9]+)!)? # epoch (?P<release>[0-9]+(?:\.[0-9]+)*) # release segment (?P<pre> # pre-release [-_\.]? (?P<pre_l>(a|b|c|rc|alpha|beta|pre|preview)) [-_\.]? (?P<pre_n>[0-9]+)? )? (?P<post> # post release (?:-(?P<post_n1>[0-9]+)) | (?: [-_\.]? (?P<post_l>post|rev|r) [-_\.]? (?P<post_n2>[0-9]+)? ) )? (?P<dev> # dev release [-_\.]? (?P<dev_l>dev) [-_\.]? (?P<dev_n>[0-9]+)? )? ) (?:\+(?P<local>[a-z0-9]+(?:[-_\.][a-z0-9]+)*))? # local version """ _regex = re.compile( r"^\s*" + VERSION_PATTERN + r"\s*$", re.VERBOSE | re.IGNORECASE, ) History¶
|
| You are visitor 01402503 — GeezerVison does not store the pages you look up. Best viewed with Netscape Navigator 4.7 or Internet Explorer 6 at 800×600. No cookies required. |