diff options
author | Florian Merz <me@fiji-flo.de> | 2021-02-11 14:46:50 +0100 |
---|---|---|
committer | Florian Merz <me@fiji-flo.de> | 2021-02-11 14:46:50 +0100 |
commit | a55b575e8089ee6cab7c5c262a7e6db55d0e34d6 (patch) | |
tree | 5032e6779a402a863654c9d65965073f09ea4182 /files/es/glossary/base64/index.html | |
parent | 8260a606c143e6b55a467edf017a56bdcd6cba7e (diff) | |
download | translated-content-a55b575e8089ee6cab7c5c262a7e6db55d0e34d6.tar.gz translated-content-a55b575e8089ee6cab7c5c262a7e6db55d0e34d6.tar.bz2 translated-content-a55b575e8089ee6cab7c5c262a7e6db55d0e34d6.zip |
unslug es: move
Diffstat (limited to 'files/es/glossary/base64/index.html')
-rw-r--r-- | files/es/glossary/base64/index.html | 345 |
1 files changed, 345 insertions, 0 deletions
diff --git a/files/es/glossary/base64/index.html b/files/es/glossary/base64/index.html new file mode 100644 index 0000000000..c8747777cd --- /dev/null +++ b/files/es/glossary/base64/index.html @@ -0,0 +1,345 @@ +--- +title: Base64 codificando y decodificando +slug: Web/API/WindowBase64/Base64_codificando_y_decodificando +translation_of: Glossary/Base64 +--- +<p><strong>Base64</strong> es un grupo de esquemas de <a href="https://es.wikipedia.org/wiki/Codificaci%C3%B3n_de_binario_a_texto">codificación de binario a texto</a> que representa los datos binarios mediante una cadena ASCII, traduciéndolos en una representación radix-64. El término <em>Base64</em> se origina de un <a href="https://es.wikipedia.org/wiki/Multipurpose_Internet_Mail_Extensions#Content-Transfer-Encoding">sistema de codificación de transmisión de contenido MIME</a> específico.</p> + +<p>Los esquemas de codificación Base64 son comúnmente usados cuando se necesita codificar datos binarios para que sean almacenados y transferidos sobre un medio diseñado para tratar con datos textuales. Esto es para asegurar que los datos se mantienen intactos y sin modificaciones durante la transmisión. Base64 es comúnmente usado en muchas aplicaciones, incluyendo la escritura de emails vía <a href="https://es.wikipedia.org/wiki/Multipurpose_Internet_Mail_Extensions">MIME</a> y el almacenamiento de datos complejos en <a href="/es/docs/XML">XML</a>.</p> + +<p>En JavaScript hay dos funciones para decodificar y codificar cadenas base64, respectivamente:</p> + +<ul> + <li>{{domxref("WindowBase64.atob","atob()")}}</li> + <li>{{domxref("WindowBase64.btoa","btoa()")}}</li> +</ul> + +<p>La función <code>atob()</code> decodifica una cadena de datos que ha sido codificada usando la codificación en base 64. Por el contrario, la función <code>btoa()</code> crea una cadena ASCII codificada en base 64 a partir de una "cadena" de datos binarios.</p> + +<p>Ambas funciones trabajan sobre cadenas de texto. Si desea trabajar con <a href="/es/docs/Web/JavaScript/Referencia/Objetos_globales/ArrayBuffer">ArrayBuffers</a>, lea <a href="/es/docs/Web/API/WindowBase64/Base64_codificando_y_decodificando$edit#Solution_.232_.E2.80.93_rewriting_atob%28%29_and_btoa%28%29_using_TypedArrays_and_UTF-8">este párrafo</a>.</p> + + + +<table class="topicpage-table"> + <tbody> + <tr> + <td> + <h2 class="Documentation" id="Documentation" name="Documentation">Documentación</h2> + + <dl> + <dt><a href="https://developer.mozilla.org/en-US/docs/data_URIs" title="https://developer.mozilla.org/en-US/docs/data_URIs"><code>data</code> URIs</a></dt> + <dd><small><code>Los URIs de</code> datos, definidos por <a class="external" href="http://tools.ietf.org/html/rfc2397" title="http://tools.ietf.org/html/rfc2397">RFC 2397</a>, permiten a los creadores de contenido introducir pequeños ficheros en línea en documentos.</small></dd> + <dt><a href="https://es.wikipedia.org/wiki/Base64" title="https://en.wikipedia.org/wiki/Base64">Base64</a></dt> + <dd><small>Artículo en Wikipedia sobre el sistema de codificación Base64.</small></dd> + <dt>{{domxref("WindowBase64.atob","atob()")}}</dt> + <dd><small>Decodifica una cadena de datos que ha sido codificada utilizando base-64.</small></dd> + <dt>{{domxref("WindowBase64.btoa","btoa()")}}</dt> + <dd><small>Crea una cadena ASCII codificada en base 64 a partir de una "cadena" de datos binarios.</small></dd> + <dt><a href="#The_.22Unicode_Problem.22">The "Unicode Problem"</a></dt> + <dd><small>En la mayoría de navegadores, llamar a <code>btoa()</code> con una cadena Unicode causará una excepción <code>Character Out Of Range</code>. Este párrafo muestra algunas soluciones.</small></dd> + <dt><a href="/en-US/docs/URIScheme" title="/en-US/docs/URIScheme">URIScheme</a></dt> + <dd><small>Lista de esquemas URI soportados por Mozilla.</small></dd> + <dt><a href="/en-US/docs/Web/JavaScript/Typed_arrays/StringView" title="/en-US/docs/Web/JavaScript/Typed_arrays/StringView"><code>StringView</code></a></dt> + <dd>En este artículo está publicada una librería hecha por nosotros con los siguientes objetivos:</dd> + <dd> + <ul> + <li>crear una interfaz al estilo de <a class="external" href="http://en.wikipedia.org/wiki/C_%28programming_language%29" title="http://en.wikipedia.org/wiki/C_%28programming_language%29">C</a> para cadenas (es decir, arrays de códigos de caracteres —<a href="/en-US/docs/Web/JavaScript/Typed_arrays/ArrayBufferView" title="/en-US/docs/Web/JavaScript/Typed_arrays/ArrayBufferView"> <code>ArrayBufferView</code></a> en JavaScript) basada en la interfaz <a href="/en-US/docs/Web/JavaScript/Typed_arrays/ArrayBuffer" title="/en-US/docs/Web/JavaScript/Typed_arrays/ArrayBuffer"><code>ArrayBuffer</code></a> de JavaScript.</li> + <li>crear una colección de métodos para los que los objetos parecidos a cadenas (de ahora en adelante, <code>stringView</code>s) funcionen estrictamente en arrays de números más que en cadenas JavaScript inmutables.</li> + <li>trabajar con otras codificaciones Unicode diferentes de las <a href="/en-US/docs/Web/API/DOMString" title="/en-US/docs/Web/API/DOMString"><code>DOMString</code></a>s UTF-16 por defecto de JavaScript.</li> + </ul> + </dd> + </dl> + + <p><span class="alllinks"><a href="/en-US/docs/tag/Base64">Ver todo...</a></span></p> + </td> + <td> + <h2 class="Tools" id="Tools" name="Tools">Herramientas</h2> + + <ul> + <li><a href="#Solution_.232_.E2.80.93_rewriting_atob()_and_btoa()_using_TypedArrays_and_UTF-8">Reescribir atob() y btoa() usando TypedArrays y UTF-8</a></li> + <li><a href="/en-US/docs/Web/JavaScript/Typed_arrays/StringView" title="/en-US/docs/Web/JavaScript/Typed_arrays/StringView"><code>StringView</code>, una representación parecida a C de cadenas basadas en arrays tipados</a><span class="alllinks"><a href="/en-US/docs/tag/Base64">View All...</a></span></li> + </ul> + + <h2 class="Related_Topics" id="Related_Topics" name="Related_Topics">Temas relacionados</h2> + + <ul> + <li><a href="/en-US/docs/Web/JavaScript/Typed_arrays/ArrayBuffer"><code>ArrayBuffer</code></a></li> + <li><a href="/en-US/docs/Web/JavaScript/Typed_arrays">Vectores o arrays tipados</a></li> + <li><a href="/en-US/docs/Web/JavaScript/Typed_arrays/ArrayBufferView">ArrayBufferView</a></li> + <li><a href="/en-US/docs/Web/JavaScript/Typed_arrays/Uint8Array"><code>Uint8Array</code></a></li> + <li><a href="https://developer.mozilla.org/en-US/docs/Web/JavaScript/Typed_arrays/StringView" title="/en-US/docs/Web/JavaScript/Typed_arrays/StringView"><code>StringView</code></a><a href="/en-US/docs/Web/JavaScript/Typed_arrays/StringView" title="/en-US/docs/Web/JavaScript/Typed_arrays/StringView">, una representación parecida a C de cadenas basadas en arrays tipados</a></li> + <li><a href="/en-US/docs/Web/API/DOMString" title="/en-US/docs/Web/API/DOMString"><code>DOMString</code></a></li> + <li><a href="/en-US/docs/URI" title="/en-US/docs/URI"><code>URI</code></a></li> + <li><a href="/en-US/docs/Web/JavaScript/Reference/Global_Objects/encodeURI" title="/en-US/docs/Web/JavaScript/Reference/Global_Objects/encodeURI"><code>encodeURI()</code></a></li> + </ul> + </td> + </tr> + </tbody> +</table> + + + +<h2 id="El_Problema_Unicode">El "Problema Unicode"</h2> + +<p>Como las <a href="/en-US/docs/Web/API/DOMString" title="/en-US/docs/Web/API/DOMString"><code>DOMString</code></a>s son cadenas codificadas en 16 bits, en la mayoría de navegadores llamar a <code>window.btoa</code> sobre una cadena Unicode resultará en una excepción <code>Character Out Of Range </code>si un carácter excede el rango de los caracteres ASCII de 8 bits. Hay dos posibles métodos para resolver este problema:</p> + +<ul> + <li>el primero es escapar la cadena completa y, entonces, codificarla;</li> + <li>el segundo es convertir la <a href="/en-US/docs/Web/API/DOMString" title="/en-US/docs/Web/API/DOMString"><code>DOMString</code></a> UTF-16 en un array de caracteres UTF-8 y codificarla.</li> +</ul> + +<p>Aquí están los dos posibles métodos:</p> + +<h3 id="Solución_1_–_escapar_la_cadena_antes_de_codificarla">Solución #1 – escapar la cadena antes de codificarla</h3> + +<pre class="brush:js notranslate">function utf8_to_b64( str ) { + return window.btoa(unescape(encodeURIComponent( str ))); +} + +function b64_to_utf8( str ) { + return decodeURIComponent(escape(window.atob( str ))); +} + +// Uso: +utf8_to_b64('✓ à la mode'); // "4pyTIMOgIGxhIG1vZGU=" +b64_to_utf8('4pyTIMOgIGxhIG1vZGU='); // "✓ à la mode"</pre> + +<p>Esta solución ha sido propuesta por <a href="http://ecmanaut.blogspot.com/2006/07/encoding-decoding-utf8-in-javascript.html">Johan Sundström</a>.</p> + +<p>Otra posible solución sin utilizar las funciones 'unscape' y 'escape', ya obsoletas.</p> + +<pre class="brush:js notranslate">function b64EncodeUnicode(str) { + return btoa(encodeURIComponent(str).replace(/%([0-9A-F]{2})/g, function(match, p1) { + return String.fromCharCode('0x' + p1); + })); +} + b64EncodeUnicode('✓ à la mode'); // "4pyTIMOgIGxhIG1vZGU=" +</pre> + +<h3 id="Solución_2_–_reescribir_atob_y_btoa_usando_TypedArrays_y_UTF-8">Solución #2 – reescribir <code>atob()</code> y <code>btoa()</code> usando <code>TypedArray</code>s y UTF-8</h3> + +<div class="note"><strong>Nota:</strong> El siguiente código también es útil para obtener un <a href="/en-US/docs/Web/JavaScript/Typed_arrays/ArrayBuffer">ArrayBuffer</a> a partir de una cadena <em>Base64</em> y/o viceversa (<a href="#Appendix.3A_Decode_a_Base64_string_to_Uint8Array_or_ArrayBuffer" title="#Appendix.3A_Decode_a_Base64_string_to_Uint8Array_or_ArrayBuffer">véase abajo</a>). <strong>Para una librería completa de arrays tipados, vea <a href="/en-US/docs/Web/JavaScript/Typed_arrays/StringView" title="/en-US/docs/Web/JavaScript/Typed_arrays/StringView">este artículo</a></strong>.</div> + +<pre class="brush: js notranslate">"use strict"; + +/*\ +|*| +|*| Base64 / binary data / UTF-8 strings utilities +|*| +|*| https://developer.mozilla.org/en-US/docs/Web/JavaScript/Base64_encoding_and_decoding +|*| +\*/ + +/* Decodificación de cadena base64 en array de bytes */ + +function b64ToUint6 (nChr) { + + return nChr > 64 && nChr < 91 ? + nChr - 65 + : nChr > 96 && nChr < 123 ? + nChr - 71 + : nChr > 47 && nChr < 58 ? + nChr + 4 + : nChr === 43 ? + 62 + : nChr === 47 ? + 63 + : + 0; + +} + +function base64DecToArr (sBase64, nBlocksSize) { + + var + sB64Enc = sBase64.replace(/[^A-Za-z0-9\+\/]/g, ""), nInLen = sB64Enc.length, + nOutLen = nBlocksSize ? Math.ceil((nInLen * 3 + 1 >> 2) / nBlocksSize) * nBlocksSize : nInLen * 3 + 1 >> 2, taBytes = new Uint8Array(nOutLen); + + for (var nMod3, nMod4, nUint24 = 0, nOutIdx = 0, nInIdx = 0; nInIdx < nInLen; nInIdx++) { + nMod4 = nInIdx & 3; + nUint24 |= b64ToUint6(sB64Enc.charCodeAt(nInIdx)) << 18 - 6 * nMod4; + if (nMod4 === 3 || nInLen - nInIdx === 1) { + for (nMod3 = 0; nMod3 < 3 && nOutIdx < nOutLen; nMod3++, nOutIdx++) { + taBytes[nOutIdx] = nUint24 >>> (16 >>> nMod3 & 24) & 255; + } + nUint24 = 0; + + } + } + + return taBytes; +} + +/* Codificación de array en una cadena Base64 */ + +function uint6ToB64 (nUint6) { + + return nUint6 < 26 ? + nUint6 + 65 + : nUint6 < 52 ? + nUint6 + 71 + : nUint6 < 62 ? + nUint6 - 4 + : nUint6 === 62 ? + 43 + : nUint6 === 63 ? + 47 + : + 65; + +} + +function base64EncArr (aBytes) { + + var nMod3 = 2, sB64Enc = ""; + + for (var nLen = aBytes.length, nUint24 = 0, nIdx = 0; nIdx < nLen; nIdx++) { + nMod3 = nIdx % 3; + if (nIdx > 0 && (nIdx * 4 / 3) % 76 === 0) { sB64Enc += "\r\n"; } + nUint24 |= aBytes[nIdx] << (16 >>> nMod3 & 24); + if (nMod3 === 2 || aBytes.length - nIdx === 1) { + sB64Enc += String.fromCharCode(uint6ToB64(nUint24 >>> 18 & 63), uint6ToB64(nUint24 >>> 12 & 63), uint6ToB64(nUint24 >>> 6 & 63), uint6ToB64(nUint24 & 63)); + nUint24 = 0; + } + } + + return sB64Enc.substr(0, sB64Enc.length - 2 + nMod3) + (nMod3 === 2 ? '' : nMod3 === 1 ? '=' : '=='); + +} + +/* De array UTF-8 a DOMString y viceversa */ + +function UTF8ArrToStr (aBytes) { + + var sView = ""; + + for (var nPart, nLen = aBytes.length, nIdx = 0; nIdx < nLen; nIdx++) { + nPart = aBytes[nIdx]; + sView += String.fromCharCode( + nPart > 251 && nPart < 254 && nIdx + 5 < nLen ? /* six bytes */ + /* (nPart - 252 << 30) may be not so safe in ECMAScript! So...: */ + (nPart - 252) * 1073741824 + (aBytes[++nIdx] - 128 << 24) + (aBytes[++nIdx] - 128 << 18) + (aBytes[++nIdx] - 128 << 12) + (aBytes[++nIdx] - 128 << 6) + aBytes[++nIdx] - 128 + : nPart > 247 && nPart < 252 && nIdx + 4 < nLen ? /* five bytes */ + (nPart - 248 << 24) + (aBytes[++nIdx] - 128 << 18) + (aBytes[++nIdx] - 128 << 12) + (aBytes[++nIdx] - 128 << 6) + aBytes[++nIdx] - 128 + : nPart > 239 && nPart < 248 && nIdx + 3 < nLen ? /* four bytes */ + (nPart - 240 << 18) + (aBytes[++nIdx] - 128 << 12) + (aBytes[++nIdx] - 128 << 6) + aBytes[++nIdx] - 128 + : nPart > 223 && nPart < 240 && nIdx + 2 < nLen ? /* three bytes */ + (nPart - 224 << 12) + (aBytes[++nIdx] - 128 << 6) + aBytes[++nIdx] - 128 + : nPart > 191 && nPart < 224 && nIdx + 1 < nLen ? /* two bytes */ + (nPart - 192 << 6) + aBytes[++nIdx] - 128 + : /* nPart < 127 ? */ /* one byte */ + nPart + ); + } + + return sView; + +} + +function strToUTF8Arr (sDOMStr) { + + var aBytes, nChr, nStrLen = sDOMStr.length, nArrLen = 0; + + /* mapeando... */ + + for (var nMapIdx = 0; nMapIdx < nStrLen; nMapIdx++) { + nChr = sDOMStr.charCodeAt(nMapIdx); + nArrLen += nChr < 0x80 ? 1 : nChr < 0x800 ? 2 : nChr < 0x10000 ? 3 : nChr < 0x200000 ? 4 : nChr < 0x4000000 ? 5 : 6; + } + + aBytes = new Uint8Array(nArrLen); + + /* transcripción... */ + + for (var nIdx = 0, nChrIdx = 0; nIdx < nArrLen; nChrIdx++) { + nChr = sDOMStr.charCodeAt(nChrIdx); + if (nChr < 128) { + /* un byte */ + aBytes[nIdx++] = nChr; + } else if (nChr < 0x800) { + /* dos bytes */ + aBytes[nIdx++] = 192 + (nChr >>> 6); + aBytes[nIdx++] = 128 + (nChr & 63); + } else if (nChr < 0x10000) { + /* tres bytes */ + aBytes[nIdx++] = 224 + (nChr >>> 12); + aBytes[nIdx++] = 128 + (nChr >>> 6 & 63); + aBytes[nIdx++] = 128 + (nChr & 63); + } else if (nChr < 0x200000) { + /* cuatro bytes */ + aBytes[nIdx++] = 240 + (nChr >>> 18); + aBytes[nIdx++] = 128 + (nChr >>> 12 & 63); + aBytes[nIdx++] = 128 + (nChr >>> 6 & 63); + aBytes[nIdx++] = 128 + (nChr & 63); + } else if (nChr < 0x4000000) { + /* cinco bytes */ + aBytes[nIdx++] = 248 + (nChr >>> 24); + aBytes[nIdx++] = 128 + (nChr >>> 18 & 63); + aBytes[nIdx++] = 128 + (nChr >>> 12 & 63); + aBytes[nIdx++] = 128 + (nChr >>> 6 & 63); + aBytes[nIdx++] = 128 + (nChr & 63); + } else /* if (nChr <= 0x7fffffff) */ { + /* seis bytes */ + aBytes[nIdx++] = 252 + (nChr >>> 30); + aBytes[nIdx++] = 128 + (nChr >>> 24 & 63); + aBytes[nIdx++] = 128 + (nChr >>> 18 & 63); + aBytes[nIdx++] = 128 + (nChr >>> 12 & 63); + aBytes[nIdx++] = 128 + (nChr >>> 6 & 63); + aBytes[nIdx++] = 128 + (nChr & 63); + } + } + + return aBytes; + +} +</pre> + +<h4 id="Tests">Tests</h4> + +<pre class="brush: js notranslate">/* Tests */ + +var sMyInput = "Base 64 \u2014 Mozilla Developer Network"; + +var aMyUTF8Input = strToUTF8Arr(sMyInput); + +var sMyBase64 = base64EncArr(aMyUTF8Input); + +alert(sMyBase64); + +var aMyUTF8Output = base64DecToArr(sMyBase64); + +var sMyOutput = UTF8ArrToStr(aMyUTF8Output); + +alert(sMyOutput);</pre> + +<h4 id="Apéndice_Decodificar_una_cadena_Base64_en_Uint8Array_o_ArrayBuffer">Apéndice: Decodificar una cadena <em>Base64</em> en <a href="/en-US/docs/Web/JavaScript/Typed_arrays/Uint8Array">Uint8Array</a> o <a href="/en-US/docs/Web/JavaScript/Typed_arrays/ArrayBuffer">ArrayBuffer</a></h4> + +<p>Estas funciones nos permiten crear también <a href="/en-US/docs/Web/JavaScript/Typed_arrays/Uint8Array">uint8Arrays</a> o <a href="/en-US/docs/Web/JavaScript/Typed_arrays/ArrayBuffer">arrayBuffers</a> a partir de cadenas codificadas en base 64:</p> + +<pre class="brush: js notranslate">var myArray = base64DecToArr("QmFzZSA2NCDigJQgTW96aWxsYSBEZXZlbG9wZXIgTmV0d29yaw=="); // "Base 64 \u2014 Mozilla Developer Network" + +var myBuffer = base64DecToArr("QmFzZSA2NCDigJQgTW96aWxsYSBEZXZlbG9wZXIgTmV0d29yaw==").buffer; // "Base 64 \u2014 Mozilla Developer Network" + +alert(myBuffer.byteLength);</pre> + +<div class="note"><strong>Nota:</strong> La función <code>base64DecToArr(sBase64[, <em>nBlocksSize</em>])</code> devuelve un <a href="/en-US/docs/Web/JavaScript/Typed_arrays/Uint8Array"><code>uint8Array</code></a> de bytes. Si tu objetivo es construir un búfer de datos crudos de 16, 32 o 64 bits, usa el argumento <code>nBlocksSize</code>, que es el número de bytes de los que la propiedad <code>uint8Array.buffer.bytesLength</code> debe devolver un múltiplo (1 u omitido para ASCII, <a href="/en-US/docs/Web/API/DOMString/Binary">cadenas binarias</a> o cadenas UTF-8 codificacas, 2 para cadenas UTF-16, 4 para cadenas UTF-32).</div> + +<p>Para una librería más completa, véase <a href="https://developer.mozilla.org/en-US/docs/Web/JavaScript/Typed_arrays/StringView" title="/en-US/docs/Web/JavaScript/Typed_arrays/StringView"><code>StringView</code></a><a href="/en-US/docs/Web/JavaScript/Typed_arrays/StringView" title="/en-US/docs/Web/JavaScript/Typed_arrays/StringView">, una representación parecida a C de cadenas basadas en arrays tipados</a>.</p> + +<h2 id="Véase_también">Véase también</h2> + +<ul> + <li>{{domxref("WindowBase64.atob","atob()")}}</li> + <li>{{domxref("WindowBase64.btoa","btoa()")}}</li> + <li><a href="/en-US/docs/data_URIs" title="/en-US/docs/data_URIs"><code>data</code> URIs</a></li> + <li><a href="/en-US/docs/Web/JavaScript/Typed_arrays/ArrayBuffer">ArrayBuffer</a></li> + <li><a href="/en-US/docs/Web/JavaScript/Typed_arrays">TypedArrays</a></li> + <li><a href="/en-US/docs/Web/JavaScript/Typed_arrays/ArrayBufferView">ArrayBufferView</a></li> + <li><a href="/en-US/docs/Web/JavaScript/Typed_arrays/Uint8Array">Uint8Array</a></li> + <li><a href="https://developer.mozilla.org/en-US/docs/Web/JavaScript/Typed_arrays/StringView" title="/en-US/docs/Web/JavaScript/Typed_arrays/StringView"><code>StringView</code> – a C-like representation of strings based on typed arrays</a></li> + <li><a href="/en-US/docs/Web/API/DOMString" title="/en-US/docs/Web/API/DOMString">DOMString</a></li> + <li><a href="/en-US/docs/URI" title="/en-US/docs/URI"><code>URI</code></a></li> + <li><a href="/en-US/docs/Web/JavaScript/Reference/Global_Objects/encodeURI" title="/en-US/docs/Web/JavaScript/Reference/Global_Objects/encodeURI"><code>encodeURI()</code></a></li> + <li><a href="/en-US/docs/XPCOM_Interface_Reference/nsIURIFixup" title="/en-US/docs/XPCOM_Interface_Reference/nsIURIFixup"><code>nsIURIFixup()</code></a></li> + <li><a href="https://en.wikipedia.org/wiki/Base64" title="https://en.wikipedia.org/wiki/Base64"><code>Base64 on Wikipedia</code></a></li> +</ul> |