誤り

符号化と復号 (文字コード)

[47] 符号化は、文字列をバイト列に変換する操作です。 復号は、バイト列を文字列に変換する操作です。

仕様書

符号化

[45] 符号化は、文字列を何らかのバイト列に変換する操作です。

[40] 符号化 (encode) は、 符号位置のストリームストリームと文字符号化符号化について、 次のようにします >>1。

  1. [41] 出力を、バイトストリームに設定します。
  2. [42] 符号化の符号化器クラスを走らせます。 入力をストリーム、出力を出力とし、 誤りモードは html とします。
  3. [43] 出力を返します。

[44] replacement、UTF-16BE、UTF-16LE を符号化とすることはできません >>1。

[53] 符号化操作が使われる場面は、 Webにおける文字コードを参照。

[46] この操作は、 Encoding Standard の規定する任意の文字符号化への符号化が必要な場合に使います。 これは後方互換性のため必要な場面に限定されています。 新しい文脈では UTF-8符号化などを用いるのが望ましいと考えられています >>1。

復号

[33] 復号は、何らかのバイト列を文字列に変換する操作です。

[3] 復号 (decode) は、 バイトストリームストリームと符号化符号化について、 次のようにします >>1。

  1. [4] バッファーを、空のバイト列に設定します。
  2. [6] 繰り返し、ストリームを読み、 バッファーの末尾に追加します。バッファーが3バイトとなるか、 end-of-stream が得られた時点でやめます。
  3. [7] バッファーの最初の3バイトが 0xEF 0xBB 0xBF なら、
    1. [8] 符号化を、 UTF-8 に設定します。
  4. [10] それ以外で、バッファーの最初の2バイトが 0xFE 0xFF なら、
    1. [11] 符号化を、 UTF-16BE に設定します。
    2. [5] バッファーが3バイトなら、
      1. [9] バッファーの最後のバイトを、ストリームにprependします。
  5. [13] それ以外で、バッファーの最初の2バイトが 0xFF 0xFE なら、
    1. [14] 符号化を、 UTF-16LE に設定します。
    2. [35] バッファーが3バイトなら、
      1. [36] バッファーの最後のバイトを、ストリームにprependします。
  6. [34] それ以外なら、
    1. [32] バッファーを、ストリームにprependします。
  7. [12] 出力を、符号位置のストリームに設定します。
  8. [16] 符号化の復号器クラスを走らせます。 入力はストリーム、出力は出力とします。
  9. [17] 出力を返します。

[31] 仕様書にはありませんが、符号化も返す必要があります。

[57] TextDecoder インターフェイスの decode メソッド >>56 は、その復号の処理の部分について、引数として

復号器オブジェクト
復号器オブジェクト
ストリーム
ストリーム
誤りモード
誤りモード (replacement または fatal)
do not flush flag
フラグ
BOM無視フラグ
フラグ
... を受け取り、次のようにします。
  1. [58] 出力を、新しいストリームに設定します。
  2. [59] 繰り返し、
    1. [60] 字句を、ストリームを読んだ結果に設定します。
    2. [61] 字句が end-of-stream で、 do not flush flag が真なら、
      1. [63] 繰り返しをここで脱出します。
    3. [62] それ以外なら、
      1. [64] 結果を、復号器オブジェクトの処理の結果に設定します。 入力はストリーム、出力を出力、 誤りモードを誤りモードとします。
      2. [65] 結果により、
        終了済み
        繰り返しをここで脱出します。
        誤り
        TypeError を投げ、ここで停止します。
  3. [67] ストリームの直列化 (serialize stream) 、すなわち、
    1. [66] ストリームを、 end-of-stream が得られるまで読み続けます。 結果を、得られた符号位置を順に連結したものに設定します。
    2. [68] 復号器オブジェクトが UTF-8、UTF-16BE、UTF-16LE のいずれかで、 BOM無視フラグが偽なら、
      1. [69] 結果の先頭が U+FEFF なら、これを除去します。
    3. [70] 結果を返します。

[71] この操作は、文字列の境界以外で分割されているかもしれない複数のバイト列を連続する1つの文字列として処理することや、 BOM の扱いを著者が指示することを想定し、他での処理よりも複雑となっています。

[84] 実際には、復号操作やUTF-8復号および関連各操作も、 入出力が1つのバイト列・文字列ではなくストリームとなる場合があり、 この操作と同じような形で実装することになると思われます。


[72] 復号操作が使われる場面は、 Webにおける文字コード参照。

[43] 復号操作は、 Encoding Standard の任意の文字符号化からの復号のために使えます。 これは後方互換性のため必要な場面に限られます。 新しい文脈では UTF-8復号を用いるのが望ましいと考えられています >>1。

[81] UTF-8復号は、復号操作を呼び出さず、 直接復号器を呼び出しています。

[37] 復号の操作は、引数として文字符号化を引き渡すことができます。 しかし入力に BOM が含まれていれば、そちらが優先されます (BOM sniffing)。

[73] 他の charset sniffing との関係については、 Webにおける文字コードを参照。

[39] この操作はしばしば HTTP で転送されたデータに適用されます。 Webにおける文字コード

[38] HTTP 仕様上は charset 引数の文字符号化の指定が BOM より優先されることになっていますが、現実にはそれでは相互運用性に問題があります。 これは意図的違反です >>1。

[83] なお、 charset 引数で指定されるのは符号化ラベルであり、 呼び出し側で適切な文字符号化に変換してから本操作を呼び出す必要があります。

符号化器と復号器

[49] Encoding Standard は、符号化器と復号器を、 文字符号化ごとに定義されるクラス的なものと、 その実現値たる個別のオブジェクト的なものの両方の意味で使っています。

[52] 符号化器クラスや復号器クラスには、 走らせる処理と取扱器が定義されています。 また復号器クラスのBOMを持つは、当該復号器の文字符号化が UTF-8、UTF-16BE、UTF-16LE のいずれかなら真で、それ以外なら偽です。

[2] 符号化器オブジェクトや復号器オブジェクトは、 いくつかの文字符号化依存の状態を持ちます。 また、処理演算が定義されています。

[50] 更に、 Web IDLインターフェイスとして TextEncoder と TextDecoder があり、それぞれ (通常の Web IDL のインターフェイス同様に) インターフェイスオブジェクト (≒ クラス) とオブジェクトが存在しています。

[51] TextEncoder や TextDecoder のオブジェクトは、 いくつかの状態を持ちます。それには符号化器オブジェクトや復号器オブジェクトも含まれます。 同時には1つのオブジェクトだけを持ちますが、時に新しいオブジェクトに差し替えられることがあります。

[21] 符号化の符号化器クラスまたは復号器クラス器を、 ストリーム入力、ストリーム出力、 誤りモードモードについて走らせる (run) には、 次のようにします >>15。

  1. [22] オブジェクトを、器の新しい実現値オブジェクトに設定します。
  2. [23] 繰り返し、
    1. [24] 結果を、処理の結果に設定します。
      オブジェクト
      オブジェクト
      字句
      入力を読んだ結果
      入力
      入力
      出力
      出力
      モード
      モード
    2. [25] 結果が継続以外なら、
      1. [26] 結果を返し、ここで停止します。

[27] 符号化器オブジェクトまたは復号器オブジェクトオブジェクトを、 字句字句、 ストリーム入力、ストリーム出力、 誤りモードモードについて処理 (process) するには、 次のようにします >>15。

  1. [28] 結果を、入力と字句についてオブジェクトのクラスの取扱器を実行した結果に設定します。
  2. [29] 結果により、
    継続、終了済み
    結果を返し、ここで停止します。
    1つ以上の字句
    結果を出力にpushします。
    誤り
    モードにより、
    replacement
    U+FFFD を出力にpushします。
    html
    &#、結果の符号位置を十進数でASCII数字で最短で表現したもの、 ; を連結したものを入力にprependします。
    fatal
    誤りを返し、ここで停止します。
  3. [30] 継続を返します。

[54] 処理は、走らせるの他に、 TextEncoder の encode メソッドでも呼びだされます。しかしUTF-8符号化 (間接的に走らせるを呼び出します。) と実質的に等価です。

[19] 符号化器や復号器の取扱器 (handler) は、 ストリームと字句を入力とします。 次のいずれかを返します。 >>15

[48] 具体的なアルゴリズムは、文字符号化ごとに規定されています。

各文字符号化の項を参照。

文脈

[18] 符号化は、符号化器 (encoder) クラスと復号器 (decoder) クラスを持ちます >>15。

ただし置換、UTF-16BE、UTF-16LEは符号化器クラスを持ちません >>15。

誤りモード

[20] 誤りモード (error mode) は、次のいずれかです >>15。

replacement (復号器、既定値)
不正な入力を U+FFFD に置換することを指定するものです。
fatal (復号器 / 符号化器、既定値)
不正な入力の時エラーを報告して停止するべきことを指定するものです。
html (符号化器)
出力の文字符号化で表現できない時 HTML の十進文字参照に置換することを指定するものです。

[75] fatal は、 XML構文解析器 >>15、 BOMなしUTF-8復号または失敗、 TextDecoder fatal で使われます。

[78] replacement はその他の復号が必要な場面で使われます。 例えばHTML構文解析器が該当します。

[74] 符号化器では実際には html しか使われません。 かつては TextEncoder で UTF-8 以外かつ fatal が指定される可能性があったようですが、現在では UTF-8 しか指定できません。 また UTF-8 はすべてのUnicodeスカラー値を誤りなく符号化できます。

サロゲートは Web IDL USVString への変換の時点で置換されます。

歴史

[76] Define 'continue' and 'break' statements (mikewest著, ) https://github.com/whatwg/infra/commit/8fbf990dcdb5f7ee80a85b569cba61a056fe1cc5

[77] Parse application/x-www-form-urlencoded using UTF-8 only (annevk著, ) https://github.com/whatwg/url/commit/3fe969679f78c92c353047661b0c4b6797f099f6

[90] Give clearer advice on hooks for standards (annevk著, ) https://github.com/whatwg/encoding/commit/b579018b406d7752f8b7a3aa9c2bc800519c6f1a

[92] Use UTF-8 decode without BOM for multipart/form-data (annevk, , ) https://github.com/whatwg/fetch/commit/7db8ac52245d6f0abaaeec6ae1cd96553c30b737