¿Cómo cargo el contenido de un archivo de texto en una variable de JavaScript?

155

Tengo un archivo de texto en la raíz de mi aplicación web http: //localhost/foo.txt y me gustaría cargarlo en una variable en javascript ... en groovy, haría esto:

def fileContents = 'http://localhost/foo.txt'.toURL().text;
println fileContents;

¿Cómo puedo obtener un resultado similar en JavaScript?

danb
fuente

Respuestas:

142

XMLHttpRequest, es decir, AJAX, sin el XML.

La manera precisa de hacerlo depende del marco de JavaScript que esté utilizando, pero si no tenemos en cuenta los problemas de interoperabilidad, su código se verá así:

cliente var = nuevo XMLHttpRequest ();
client.open ('GET', '/foo.txt');
client.onreadystatechange = function () {
  alerta (client.responseText);
}
client.send ();

Sin embargo, normalmente hablando, XMLHttpRequest no está disponible en todas las plataformas, por lo que se realiza un poco de falsificación. Una vez más, su mejor opción es usar un marco AJAX como jQuery.

Una consideración adicional: esto solo funcionará mientras foo.txt esté en el mismo dominio. Si está en un dominio diferente, las políticas de seguridad del mismo origen le impedirán leer el resultado.

Edward Z. Yang
fuente
1
Una solución alternativa para la política del mismo origen es usar JSONP que también es compatible con jQuery (para la parte del cliente)
OneWorld
3
podría ser útil agregar que, dentro de onreadystatechange, puede acceder a la propiedad readystate del objeto XMLHttpRequest (en el ejemplo: client.readystate) para saber cuál es el estado, ya que el evento onreadystatechange se genera para cargar, cargar, ... .. por lo que debe esperar a client.readystate == 4 dentro de onreadystatechange antes de poder usar client.responseText.
GameAlchemist
2
@GameAlchemist: tropecé con tu gran respuesta. Sólo quería tener en cuenta que en la mayoría de los navegadores readyState está entubado camello, por lo que el código debe ser algo como esto:if (client.readyState === 4){ }
snorpey
66
Además, puede hacer client.onloadendy obtener los datos completos
Athena
2
La respuesta debe redactarse para incluir la verificación del client.readyStatevalor de la propiedad. Lo rechazo hasta que sea así, la gente no va a leer los comentarios para descubrir que la respuesta es solo parcialmente correcta.
amn
84

así es como lo hice en jquery:

jQuery.get('http://localhost/foo.txt', function(data) {
    alert(data);
});
danb
fuente
eso no parece trabajar con datos de texto sin formato tabular ( docs.jquery.com/Specifying_the_Data_Type_for_AJAX_Requests )
pez globo
77
Tenga en cuenta que esto no funciona si se está probando a nivel local utilizando file://es decir: file:///example.com/foo.html. Firefox se queja de un error de sintaxis y de bloques de Chrome porque lo considera una solicitud de origen cruzado.
Akronix
@pufferfish funcionará con datos simples si especifica el dataTypeparámetro, consulte api.jquery.com/jQuery.get/
yvesonline
1
@Akronix si omite la http://...parte, porque vive en el mismo dominio, funcionará, por ejemplo jQuery.get("foo.txt", ...).
yvesonline
@Akronix ¿Hay una manera fácil de probarlo localmente? Sigo recibiendo errores de solicitud de origen
cruzado
50

Actualización 2019: Uso de Fetch:

fetch('http://localhost/foo.txt')
  .then(response => response.text())
  .then((data) => {
    console.log(data)
  })

https://developer.mozilla.org/en-US/docs/Web/API/Fetch_API

Vic
fuente
44
Sí, Fetch es un estándar (reciente), no una extensión patentada.
Laurent Caillette
1
Es 2019, y buscar es algo hermoso. Esta es LA forma para todos los navegadores modernos, incluido Samsung Internet, que acaba de ponerse al día ...
Dave Everitt
Un código compacto y funcional, Vic, gracias. Para lograr el manejo de errores, ¿sería posible poner algo response.ok(o equivalente) en algún lugar de su código? No tengo mucha experiencia fetch, así que no sé el lugar exacto para configurarlo.
Sopalajo de Arrierez
Gran solución Esto fue súper fácil incluso para un principiante completo. Almacenado en variable en lugar de console.log en el último paso, ahora puede usarlo en cualquier lugar.
AveryFreeman
27

Si solo desea una cadena constante del archivo de texto, puede incluirla como JavaScript:

// This becomes the content of your foo.txt file
let text = `
My test text goes here!
`;
<script src="foo.txt"></script>
<script>
  console.log(text);
</script>

La cadena cargada desde el archivo se vuelve accesible para JavaScript después de ser cargada. El carácter `(retroceso) comienza y finaliza una plantilla literal , permitiendo tanto los caracteres" como "en su bloque de texto.

Este enfoque funciona bien cuando intenta cargar un archivo localmente, ya que Chrome no permitirá AJAX en las URL con el file://esquema.

Erik Uggeldahl
fuente
1
Esta sería una solución realmente ingeniosa. Pero la plantilla literal no es compatible con IE11 y la variable "let" estaría fuera de alcance dentro de un bloque de funciones, por lo que esta implementación está cargada de peligros.
Neville
7

Una cosa a tener en cuenta es que Javascript se ejecuta en el cliente y no en el servidor. Realmente no se puede "cargar un archivo" desde el servidor en Javascript. Lo que sucede es que Javascript envía una solicitud al servidor, y el servidor devuelve el contenido del archivo solicitado. ¿Cómo recibe Javascript los contenidos? Para eso es la función de devolución de llamada. En el caso de Edward, eso es

    client.onreadystatechange = function() {

y en el caso de danb, es

 function(data) {

Esta función se llama cada vez que llegan los datos. La versión de jQuery usa Ajax implícitamente, simplemente facilita la codificación encapsulando ese código en la biblioteca.

atmelino
fuente
7

Actualización 2020: Uso de Fetch con async / await

const response = await fetch('http://localhost/foo.txt');
const data = await response.text();
console.log(data);

Tenga en cuenta que awaitsolo se puede usar en una asyncfunción. Un ejemplo más largo podría ser

async function loadFileAndPrintToConsole(url) {
  try {
    const response = await fetch(url);
    const data = await response.text();
    console.log(data);
  } catch (err) {
    console.error(err);
  }
}

loadFileAndPrintToConsole('https://threejsfundamentals.org/LICENSE');

gman
fuente
5

Esto debería funcionar en casi todos los navegadores:

var xhr=new XMLHttpRequest();
xhr.open("GET","https://12Me21.github.io/test.txt");
xhr.onload=function(){
    console.log(xhr.responseText);
}
xhr.send();

Además, está la nueva FetchAPI:

fetch("https://12Me21.github.io/test.txt")
.then( response => response.text() )
.then( text => console.log(text) )
12Me21
fuente
1

Cuando se trabaja con jQuery, en lugar de usar jQuery.get, p. Ej.

jQuery.get("foo.txt", undefined, function(data) {
    alert(data);
}, "html").done(function() {
    alert("second success");
}).fail(function(jqXHR, textStatus) {
    alert(textStatus);
}).always(function() {
    alert("finished");
});

podría usar lo .loadque le da una forma mucho más condensada:

$("#myelement").load("foo.txt");

.loadtambién le ofrece la opción de cargar páginas parciales que pueden ser útiles, consulte api.jquery.com/load/ .

yvesonline
fuente
-3

Si su entrada fue estructurada como XML, puede usar la importXMLfunción. (Más información aquí en quirksmode ).

Si no es XML, y no hay una función equivalente para importar texto plano, entonces puede abrirlo en un iframe oculto y luego leer el contenido desde allí.

nickf
fuente