URL de cuadro vagabundo para archivo de metadatos JSON

18

En mi Vagrantfile, puedo especificar la URL de un cuadro:

config.vm.box_url = "http://example.com/my-box.pkg"

De acuerdo con la documentación más reciente , debería poder crear un archivo JSON que contenga las URL para diferentes versiones de la caja. La documentación también dice que puedo usar la URL de este archivo JSON cuando se ejecuta vagrant box add. Esperaba poder usar la URL de ese archivo JSON para config.vm.box_url. Sin embargo, eso no parece funcionar. Cuando lo intento, lo trata como un archivo de cuadro:

Bringing machine 'default' up with 'virtualbox' provider...
==> default: Box 'my-box' could not be found. Attempting to find and install...
    default: Box Provider: virtualbox
    default: Box Version: >= 0
==> default: Adding box 'my-box' (v0) for provider: virtualbox
    default: Downloading: http://example.com/my-box.pkg.json
    default: Progress: 100% (Rate: 876k/s, Estimated time remaining: 0:00:01)
The box failed to unpackage properly. Please verify that the box
file you're trying to add is not corrupted and try again. The
output from attempting to unpackage (if any):

bsdtar.EXE: Unrecognized archive format: Illegal byte sequence
bsdtar.EXE: Error exit delayed from previous errors.

¿Es posible decirle a Vagrant que use un archivo JSON de metadatos de cuadro en mi archivo Vagrant? Prefiero no tener que usar Vagrant Cloud.

Puntilla
fuente
¿Alguna vez encontraste una solución para esto?
Jim Rubenstein
@JimRubenstein Lamentablemente, no. La sugerencia de Nicholas podría funcionar, pero estoy bastante seguro de que mi servidor ya está enviando los encabezados de tipo de contenido correctos para JSON. La respuesta de Chux puede ser precisa, pero aún no estoy convencido, ya que la documentación implica lo contrario. Desafortunadamente, la documentación de Vagrant es bastante terrible en todos lados y no da mucho contexto entre los niveles básicos de tutorial y contribuir al proyecto y pasar el rato en IRC ... al menos para mí de todos modos.
Brad
Estoy probando algo mientras hablamos sobre la publicación de un cuadro + metadatos para ver si puedo imitar el comportamiento de la nube vagabunda, localmente. Te diré cómo resulta.
Jim Rubenstein

Respuestas:

8

A partir de hoy (2016-07-12, vagabundo 1.8.4), si desea ejecutar su propio catálogo de forma manual (es decir, actualizar manualmente los cuadros y editar el archivo metadata.json), pero aún así debe comportarse como un catálogo real, tenga en cuenta lo siguiente:

  • No es necesario que el archivo se llame "metadata.json". Se puede nombrar cualquier cosa, siempre que contenga los valores esperados. Estoy usando "metadata.json" aquí para aclarar los pasos más abajo.

  • cada archivo metadata.json solo puede contener una sola casilla. Puede tener múltiples versiones, y cada versión puede tener múltiples proveedores (virtualbox, vmware, libvirt). Si necesita tener más de un cuadro (por ejemplo, "fedora" y "ubuntu"), necesita dos archivos de metadatos diferentes.

  • Vagrant espera que el archivo metadata.json tenga un tipo de "application / json" (como mencionó Nicholas Hinds anteriormente. Si su servidor web no lo devuelve (o devuelve "text / plain"), vagrant asumirá que es un archivo de caja real , e intenta analizarlo (y falla miserablemente).

  • El Atlas de Hashicorp (lo que solía ser Vagrant Cloud) es la excepción a esto, ya que las redirecciones lo llevan al contenido que se sirve como "texto / html". Mi mejor suposición para esto es que tiene algo que ver con los redireccionamientos (más sobre esto a continuación).

  • El archivo de cuadro no necesita estar en el mismo lugar que el archivo de metadatos. Puede tener su archivo de metadatos en un servidor web local y el cuadro en Amazon S3, no hay problema con eso.

Entonces, hasta donde pude, encontré que la manera más fácil de hacer que esto funcione en un servidor web y aún tener una funcionalidad bastante normal es hacer esto:

En su servidor web, cree una estructura de archivos y directorios similar a esta:

d wwwroot/
d wwwroot/boxes
d wwwroot/boxes/yourname
f wwwroot/boxes/yourname/.htaccess
d wwwroot/boxes/yourname/box1
f wwwroot/boxes/yourname/box1/metadata.json
f wwwroot/boxes/yourname/box1/box1-$version1-$provider.box
f wwwroot/boxes/yourname/box1/box1-$version2-$provider.box
f wwwroot/boxes/yourname/box1/box1-$version2-$otherprovider.box
d wwwroot/boxes/yourname/box2
f wwwroot/boxes/yourname/box2/metadata.json
f wwwroot/boxes/yourname/box2/box2-$version1-$provider.box
(... etc)

(este diseño significa que su "metadata.json" para box1 tendrá que tener sus URL apuntando a algo como " http: // yourhost / boxes / yourname / box1 / box1- $ version1- $ provider.box")

En su .htaccess, asegúrese de que "metadata.json" esté configurado para el índice del Directorio. El resto es opcional, para caché negativa y ocultar el contenido real:

Header unset Pragma
FileETag None
Header unset ETag
DirectoryIndex metadata.json
IndexIgnore *
Header set Cache-Control "max-age=0, no-cache, no-store, must-revalidate, private"
Header set Pragma "no-cache"
Header set Expires "Wed, 11 Jan 1984 05:00:00 GMT"

En su entorno, exporte el VAGRANT_SERVER_URL apuntando a su webhost. Tenga en cuenta que no hay barra diagonal final!

export VAGRANT_SERVER_URL="http://yourhost/boxes"

Con esto en su lugar (y todos los archivos con el contenido correcto), puede ir y agregar su caja directamente:

vagrant box add yourname/box1

Dado que "metadata.json" es el archivo de índice para el directorio box1, debe redirigir el contenido directamente a él, vagabundo lo recogerá, interpretará los metadatos y descargará el cuadro apropiado.

Guto Andreollo
fuente
19

Después de leer su pregunta nuevamente, parece que está tratando de hacer algo un poco diferente a lo que soy yo, pero creo que nuestro objetivo final es el mismo.

No quiero utilizar el servicio Vagrant Cloud para alojar mis cajas base, pero quiero poder distribuir un entorno de desarrollo a mi equipo de desarrollo y utilizar las características de metadata.json archivo para mantener un sistema de versiones para el entorno de desarrollo, que estará disponible para mi equipo de desarrollo simplemente usando las instalaciones integradas en vagabundo.

La documentación vagabunda es realmente escasa en esta área al momento de escribir este artículo (8/5/2014), presumiblemente porque es una característica relativamente nueva, pero estoy seguro de que el hecho de que VagrantCloud tiene un nivel pago también tiene algo que ver con eso. .

Para descubrir cómo utilizar el metadata.jsonarchivo para la versión y distribuir cuadros, eché un vistazo a algunas de las máquinas virtuales disponibles en VagrantCloud. Después de revisarlos y leer algunos de los códigos vagabundos, se hizo bastante fácil descubrir cómo lograr mi objetivo.

  • Empaquete su caja como lo haría normalmente. En mi caso, estoy empaquetando solo para la caja virtual, porque eso es lo que nuestros desarrolladores usarán para ejecutar el Vm. También empaqueto un Vagrantfile con mi basebox que realiza algunas provisiones para el entorno de desarrollo (configuración de recursos compartidos en las carpetas apropiadas, algunas configuraciones básicas de apache, registro de errores, etc.)
  • Cree un metadata.jsonarchivo para describir su cuadro base, el mío se parece a esto:

    {
        "description": "long box description",
        "short_description": "short box description",
        "name": "company/developer-environment",
        "versions": [{
            "version": "1",
            "status": "active",
            "description_html": "<p>Dev Environment</p>",
            "description_markdown": "Dev Environment",
            "providers": [{
                "name": "virtualbox",
                "url": "http:\/\/vagrant.domain.local/dev/company-developer-environment-1.box"
            }]
        }]
    }
    

Una vez que creé mi metadata.jsonarchivo, lo cargué en un servidor local que se ejecuta en nuestra red interna ( vagrant.domain.local/metadata.json). Una vez que hice eso, todo lo que quedaba era probarlo con vagabundo:

# add the box to vagrant using the definition from metadata.json
# (the box is actually downloaded here, so it can take a minute...or 10)
$ vagrant box add http://vagrant.domain.local/dev/metadata.json

# init the box (this creates a .vagrant folder and a Vagrantfile in the cwd with the appropriate box name)
$ vagrant init company/developer-environment

# boot the box
$ vagrant up

Voila, una caja privada remotamente alojada, compartida y versionada que no requiere el uso de Vagrant Cloud.

A medida que crea nuevas versiones de su caja, la empaqueta y edita el metadata.jsonarchivo. Por lo que puedo decir, puede usar cualquier esquema de versiones que desee, ya sea versiones semánticas (1.0.0, 1.0.1, etc.) o simplemente números enteros simples para las versiones (1, 2, 3, etc.). Cuando los usuarios de su caja vagrant upvagabundos comprueban automáticamente su archivo metadata.json para una nueva versión, y les pedirá vagrant box updateque actualicen la caja.

También puede omitir los bits vagrant box add <metadata.json url>y vagrant initdefiniendo un Vagrantfile base con el nombre del cuadro y la url del cuadro, así:

# -*- mode: ruby -*-
# vi: set ft=ruby :

# Vagrantfile API/syntax version. Don't touch unless you know what you're doing!
VAGRANTFILE_API_VERSION = "2"

Vagrant.configure(VAGRANTFILE_API_VERSION) do |config|
  config.vm.box = "company/developer-environment"
  config.vm.box_url = "https://vagrant.domain.local/dev/metadata.json"
end

Podría distribuir un Vagrantfile con esos contenidos, y todos los usuarios simplemente podrían hacerlo vagrant up. Sin embargo, no estoy seguro de cómo funciona cuando se actualizan las versiones.

Jim Rubenstein
fuente
Eso es perfecto, gracias! Sin embargo ... ¿cómo agrego esa URL JSON al Vagrantfile?
Brad
No necesitas hacerlo. Cuando agrega el cuadro, Vagrant descarga la imagen del cuadro actual y almacena la información ~/.vagrant.d/boxes/<your box name>. Dentro de esa carpeta está el metadata_urlarchivo al que se hace referencia alrededor de la documentación, que contiene la URL de su archivo JSON que define sus versiones. Vagrant maneja todo eso automáticamente, por lo que todo lo que tiene que hacer es vagrant box add <your metadata.json url>, entonces vagrant init <boxname> && vagrant up, vagabundo hace el resto
Jim Rubenstein
Entiendo eso, pero estoy tratando de hacer que sea lo más fácil posible para los desarrolladores ponerse en marcha. Al agregar una URL de cuadro en el Vagrantfile, no vagrant box addes necesario. Si pudiera establecer la URL de ese archivo JSON en el archivo Vagrant, ese es un paso menos para que un nuevo desarrollador simplemente se una al equipo para comenzar a funcionar. Funciona para cajas, pero no puedo entender por qué no funciona para el archivo JSON.
Brad
1
ah, entiendo, en realidad acabo de encontrar una solución para eso solo tirando pedos. debe definir config.vm.boxY config.vm.box_urldónde boxestá el nombre de su casilla y box_urlla URL de su archivo json.
Jim Rubenstein
1
@JimRubenstein Respuesta fantástica: al igual que Ricitos de Oro, no demasiado corta, ni demasiado larga :)
Steve Jansen
9

Vagrant requiere que las URL de metadatos de la caja se sirvan con el application/jsontipo de contenido. El error que está recibiendo indica que el vagabundo ha interpretado su URL como un cuadro normal.

Asegúrese de que su servidor HTTP esté configurando el Content-Typeencabezado adecuadamente. La mayoría de los servidores HTTP establecerán automáticamente el Content-Type encabezado application/jsonsi su archivo tiene la extensión.json

Nicholas Hinds
fuente
1
No sé por qué su respuesta no es la respuesta porque esto es exactamente lo que necesitaba hacer para que el aprovisionamiento local funcione con Vagrant.
Gaurav
4

Creo que tienes sus directivas mezcladas ...

Lo siguiente está tomado del sitio web vagabundo:


ARCHIVO DE CAJA

El archivo de caja real es la porción requerida para Vagrant. Se recomienda que siempre use un archivo de metadatos junto con un archivo de cuadro, pero los archivos de cuadro directo son compatibles por motivos heredados en Vagrant.

Box files are compressed using tar, tar.gz, or zip. The contents of the archive can be anything, and is specific to each provider. El núcleo vagabundo solo desempaqueta las cajas para su uso posterior.

Within the archive, Vagrant does expect a single file: "metadata.json".Este es un archivo JSON que no tiene ninguna relación con el componente de "metadatos de cuadro" anterior. This file must contain at least the "provider" key with the provider the box is for. Por ejemplo, si su caja fuera para VirtualBox, el metadata.json se vería así:

{
  "proveedor": "virtualbox"
}

If there is no metadata.json file or the file does not contain valid JSON with at least a "provider" key, then Vagrant will error when adding the box.


Entonces, creo que su formato de archivo de caja probablemente sea incorrecto. O no está comprimido con el formato recomendado, o no ha incluido un archivo metadata.json dentro del archivo

Chux Uzoeto
fuente
Para otros con el mismo problema, la ruta metadata.json (en Windows) es ..Users \ username \ vagrant.d \ boxes \ boxname \ 0 \ virtualbox \ metadata.json
Nebojsac
1

Puedes probar https://github.com/sparkoo/boxitory . Es simple un servidor jar. Lo señala al directorio donde tiene sus cuadros de vagabundo y crea una interfaz http compatible para vagabundo. Luego simplemente lo señala desde su archivo vagabundo y listo. No tiene que manejar manualmente los archivos json que describen sus cajas, agregando nuevas versiones, proveedores, etc. Todo se hace de forma gratuita. Simplemente agregue un nuevo archivo box y Boxitory lo devuelve instantáneamente cuando se lo solicite.

Michal Vala
fuente